package com.label.Service.Impl;

import cn.hutool.core.bean.BeanUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.label.Dao.RoleMapper;
import com.label.Dao.UserMapper;
import com.label.Model.Do.User;
import com.label.Model.Query.UserQuery;
import com.label.Service.RoleService;
import com.label.Service.UserService;
import com.label.Utils.Common.AesCipherUtil;
import com.label.Utils.Common.RedisUtil;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.CachePut;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.stereotype.Component;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

@Service
@Transactional(rollbackFor = {Exception.class})
public class UserServiceImpl extends ServiceImpl<UserMapper, User> implements UserService {

    @Resource
    private UserMapper userMapper;

    @Resource
    private RoleService roleService;

    @Override
    public List<User> getAll() {
        return userMapper.getUserById(null);
    }

    @Override
    @Cacheable(value = "user",key = "'id'+#userQuery.id")
    public List<User> getById(UserQuery userQuery) {
        System.out.println("数据库");
        return userMapper.getUserById(userQuery.getId());
    }

    @Override
    public List<User> getAllUserByAccount(UserQuery userQuery) {
        return userMapper.getAllUserByAccount(userQuery.getAccount());
    }

    @Override
    public List<User> getAllUserByRoles(UserQuery userQuery) {
        return userMapper.getUserByRole(userQuery.getRoles().stream().map(String::valueOf).collect(Collectors.toList()));
    }

    @Override
    @Cacheable(value = "user",key = "'account'+#userQuery.account")
    public User getOneUserByAccount(UserQuery userQuery) {
        return userMapper.getOneUserByAccount(userQuery.getAccount());
    }

    @Override
    public Boolean addUser(UserQuery userQuery) throws Exception{
        if(userMapper.selectOne(new QueryWrapper<User>().lambda().eq(User::getAccount,userQuery.getAccount()))!=null)
            return false;

        User user= BeanUtil.copyProperties(userQuery,User.class,"roles");
        String key = AesCipherUtil.enCrypto(userQuery.getAccount() + userQuery.getPassword());
        user.setPassword(key);
        userMapper.insert(user);
        if (userQuery.getRoles() != null && !userQuery.getRoles().isEmpty())
            userMapper.saveUserRole(String.valueOf(user.getId()), userQuery.getRoles().stream().map(String::valueOf).collect(Collectors.toList()));
        return true;
    }

    @Override
    @CacheEvict(value = "user",key = "'account'+#userQuery.account")
    public Boolean deleteUserById(UserQuery userQuery) {
        if(userMapper.getUserById(userQuery.getId()).isEmpty())
            return false;
        userMapper.delUserRole(String.valueOf(userQuery.getId()));
        userMapper.deleteById(userQuery.getId());
        return true;
    }

    @Override
    @CachePut(value = "user",key = "'id'+#userQuery.id")
    public Boolean updateUserById(UserQuery userQuery) {
        if(userMapper.getUserById(userQuery.getId()).isEmpty())
            return false;
        if(!BeanUtil.isEmpty(userQuery,"roles","id")){
            User user=BeanUtil.copyProperties(userQuery,User.class,"roles");
            userMapper.updateById(user);
        }
        if(userQuery.getRoles()!=null){
            userMapper.delUserRole(String.valueOf(userQuery.getId()));
            RedisUtil.delKey("role:userId_"+userQuery.getId());
            if(!userQuery.getRoles().isEmpty()){
                userMapper.saveUserRole(String.valueOf(userQuery.getId()), userQuery.getRoles().stream().map(String::valueOf).collect(Collectors.toList()));
            }
        }
        return true;
    }

    @Override
    public List<User> userSearch(UserQuery userQuery) {
        QueryWrapper<User> queryWrapper=new QueryWrapper<>();
        if (userQuery.getAccount() != null) {
            queryWrapper.lambda().like(User::getAccount, userQuery.getAccount());
        }
        if (userQuery.getSchoolId() != null) {
            queryWrapper.lambda().eq(User::getSchoolId, userQuery.getSchoolId());
        }
        if (userQuery.getUnitId() != null) {
            queryWrapper.lambda().eq(User::getUnitId, userQuery.getUnitId());
        }
        if (userQuery.getUserName() != null) {
            queryWrapper.lambda().like(User::getUserName, userQuery.getUserName());
        }
        List<User> users=userMapper.selectList(queryWrapper);
        users.forEach(p->{p.setRoles(roleService.getRoleByUser(p.getId()));});
        return users;
    }

    @Override
    public Boolean userChangePass(UserQuery userQuery) {
        User userTemp=userMapper.getOneUserByAccount(userQuery.getAccount());
        if(userTemp==null)
            return null;
        String key = AesCipherUtil.deCrypto(userTemp.getPassword());
        if (key.equals(userQuery.getAccount() + userQuery.getOldpassword())) {
            String newKey = AesCipherUtil.enCrypto(userQuery.getAccount() + userQuery.getPassword());
            User user=new User();
            user.setPassword(newKey);
            user.setId(userTemp.getId());
            userMapper.updateById(user);
            return true;
        }else
            return false;
    }


}
